home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Aminet 1 (Walnut Creek)
/
Aminet - June 1993 [Walnut Creek].iso
/
usenet
/
sources
/
volume2
/
keyboard
/
dasm20.2
< prev
next >
Wrap
Text File
|
1992-04-19
|
63KB
|
2,591 lines
Path: xanth!nic.MR.NET!tank!ncar!mailrus!ulowell!page
From: page@swan.ulowell.edu (Bob Page)
Newsgroups: comp.sources.amiga
Subject: v02i028: dasm - small systems cross assembler V2.0, Part02/03
Message-ID: <9879@swan.ulowell.edu>
Date: 26 Oct 88 17:22:29 GMT
Organization: University of Lowell, Computer Science Dept.
Lines: 2580
Approved: page@swan.ulowell.edu
Submitted-by: dillon@cory.berkeley.edu (Matt Dillon)
Posting-number: Volume 2, Issue 28
Archive-name: languages/dasm20.2
# This is a shell archive. Remove anything before this line
# then unpack it by saving it in a file and typing "sh file"
# (Files unpacked will be owned by you and have default permissions).
# This archive contains the following files:
# src/asm.h
# src/ops.c
# src/mne6502.c
# src/mne6811.c
# src/main.c
#
if `test ! -d src`
then
mkdir src
echo "mkdir src"
fi
if `test ! -s src/asm.h`
then
echo "writing src/asm.h"
cat > src/asm.h << '\Rogue\Monster\'
/*
* ASM65.H
*
* (c)Copyright 1988, Matthew Dillon, All Rights Reserved.
*
* Structures and definitions
*/
#include <stdio.h>
#ifdef UNIX
#define bmov(s,d,n) bcopy(s,d,n)
#define bset(s,n,c) xbset(s,n,c)
#endif
#ifdef IBM
#define bmov(s,d,n) movmem(s,d,(int)n)
#define bset(s,n,c) setmem(s,(int)n,(int)c)
#define bzero(s,n) setmem(s,(int)n,0)
#endif
#ifdef IBM
typedef char ubyte;
typedef unsigned uword;
typedef long ulong;
typedef int void;
#else
typedef unsigned char ubyte;
typedef unsigned short uword;
typedef unsigned long ulong;
#endif
#define MNE struct _MNE
#define MACRO struct _MACRO
#define INCFILE struct _INCFILE
#define REPLOOP struct _REPLOOP
#define IFSTACK struct _IFSTACK
#define SEGMENT struct _SEGMENT
#define SYMBOL struct _SYMBOL
#define STRLIST struct _STRLIST
#define DEFORGFILL 255
#define SHASHSIZE 1024
#define MHASHSIZE 1024
#define SHASHAND 0x03FF
#define MHASHAND 0x03FF
#define ALLOCSIZE 16384
#define MAXMACLEVEL 32
#define TAB 9
#define OUTFORM1 0
#define OUTFORM2 1
#define OUTFORM3 2
#define AM_IMP 0 /* implied */
#define AM_IMM8 1 /* immediate 8 bits */
#define AM_IMM16 2 /* immediate 16 bits */
#define AM_BYTEADR 3 /* address 8 bits */
#define AM_BYTEADRX 4 /* address 16 bits */
#define AM_BYTEADRY 5 /* relative 8 bits */
#define AM_WORDADR 6 /* index x 0 bits */
#define AM_WORDADRX 7 /* index x 8 bits */
#define AM_WORDADRY 8 /* index x 16 bits */
#define AM_REL 9 /* bit inst. special */
#define AM_INDBYTEX 10 /* bit-bra inst. spec. */
#define AM_INDBYTEY 11 /* index y 0 bits */
#define AM_INDWORD 12 /* index y 8 bits */
#define AM_0X 13 /* index x 0 bits */
#define AM_0Y 14 /* index y 0 bits */
#define AM_BITMOD 15 /* ind addr 8 bits */
#define AM_BITBRAMOD 16 /* ind addr 16 bits */
#define NUMOC 17
#define AF_IMP (1L << 0 )
#define AF_IMM8 (1L << 1 )
#define AF_IMM16 (1L << 2 )
#define AF_BYTEADR (1L << 3 )
#define AF_BYTEADRX (1L << 4 )
#define AF_BYTEADRY (1L << 5 )
#define AF_WORDADR (1L << 6 )
#define AF_WORDADRX (1L << 7 )
#define AF_WORDADRY (1L << 8 )
#define AF_REL (1L << 9 )
#define AF_INDBYTEX (1L << 10)
#define AF_INDBYTEY (1L << 11)
#define AF_INDWORD (1L << 12)
#define AF_0X (1L << 13)
#define AF_0Y (1L << 14)
#define AF_BITMOD (1L << 15)
#define AF_BITBRAMOD (1L << 16)
#define AM_SYMBOL (NUMOC+0)
#define AM_EXPLIST (NUMOC+1)
#define AM_BYTE AM_BYTEADR
#define AM_WORD AM_WORDADR
#define AM_LONG (NUMOC+2)
#define AM_BSS (NUMOC+3)
STRLIST {
STRLIST *next;
ubyte buf[4];
};
#define MF_IF 0x04
#define MF_MACRO 0x08
#define MF_MASK 0x10 /* has mask argument (byte) */
#define MF_REL 0x20 /* has rel. address (byte) */
#define MF_IMOD 0x40 /* instruction byte mod. */
MNE {
MNE *next; /* hash */
void (*vect)(); /* dispatch */
char *name; /* actual name */
ubyte flags; /* special flags */
ulong okmask;
uword opcode[NUMOC]; /* hex codes, byte or word (>xFF) opcodes */
};
MACRO {
MACRO *next;
void (*vect)();
ubyte *name;
ubyte flags;
STRLIST *strlist;
};
#define INF_MACRO 0x01
INCFILE {
INCFILE *next; /* previously pushed context */
ubyte *name; /* file name */
FILE *fi; /* file handle */
ulong lineno; /* line number in file */
ubyte flags; /* flags (macro) */
/* Only if Macro */
STRLIST *args; /* arguments to macro */
STRLIST *strlist; /* current string list */
ulong saveidx; /* save localindex */
};
#define RPF_UNKNOWN 0x01 /* value unknown */
REPLOOP {
REPLOOP *next; /* previously pushed context */
ulong count; /* repeat count */
ulong seek; /* seek to top of repeat */
ulong lineno; /* line number of line before */
INCFILE *file; /* which include file are we in*/
ubyte flags;
};
#define IFF_UNKNOWN 0x01 /* value unknown */
#define IFF_BASE 0x04
IFSTACK {
IFSTACK *next; /* previous IF */
INCFILE *file; /* which include file are we in*/
ubyte flags;
ubyte true; /* 1 if true, 0 if false */
ubyte acctrue;/* accumulatively true (not incl this one) */
};
#define SF_UNKNOWN 0x01 /* ORG unknown */
#define SF_REF 0x04 /* ORG referenced */
#define SF_BSS 0x10 /* uninitialized area (U flag) */
#define SF_RORG 0x20 /* relocatable origin active */
SEGMENT {
SEGMENT *next; /* next segment in segment list */
ubyte *name; /* name of segment */
ubyte flags; /* for ORG */
ubyte rflags; /* for RORG */
ulong org; /* current org */
ulong rorg; /* current rorg */
ulong initorg;
ulong initrorg;
ubyte initflags;
ubyte initrflags;
};
#define SYM_UNKNOWN 0x01 /* value unknown */
#define SYM_REF 0x04 /* referenced */
#define SYM_STRING 0x08 /* result is a string */
#define SYM_SET 0x10 /* SET instruction used */
#define SYM_MACRO 0x20 /* symbol is a macro */
#define SYM_MASREF 0x40 /* master reference */
SYMBOL {
SYMBOL *next; /* next symbol in hash list */
ubyte *name; /* symbol name or string if expr. */
ubyte *string; /* if symbol is actually a string */
ubyte flags; /* flags */
ubyte addrmode; /* addressing mode (expressions) */
ulong value; /* current value */
uword namelen; /* name length */
};
extern SYMBOL *SHash[];
extern MNE *MHash[];
extern INCFILE *Incfile;
extern REPLOOP *Reploop;
extern SEGMENT *Seglist;
extern IFSTACK *Ifstack;
extern SEGMENT *Csegment; /* current segment */
extern ubyte *Av[];
extern ubyte Avbuf[];
extern uword Adrbytes[];
extern uword Cvt[];
extern uword Opsize[];
extern uword Mnext; /* mnemonic extension */
extern uword Mlevel;
extern void fseek();
extern long ftell();
extern ubyte *malloc(), *zmalloc(), *strcpy(), *permalloc();
extern ubyte *sftos();
extern SYMBOL *allocsymbol();
extern ubyte Xtrace;
extern ubyte Xdebug;
extern ubyte MsbOrder;
extern ubyte Outputformat;
extern ulong Redo, Redo_why, Redo_eval;
extern ulong Localindex, Lastlocalindex;
extern ubyte F_format;
extern ubyte F_verbose;
extern char *F_outfile;
extern char *F_listfile;
extern char *F_symfile;
extern char *F_temppath;
extern FILE *FI_listfile;
extern FILE *FI_temp;
extern ubyte Fisclear;
extern ulong Plab, Pflags;
extern char Inclevel;
extern char ListMode;
extern ulong Processor;
extern SYMBOL *findsymbol(), *createsymbol(), *eval();
extern uword _fmode;
extern ulong CheckSum;
\Rogue\Monster\
else
echo "will not over write src/asm.h"
fi
if [ `wc -c src/asm.h | awk '{printf $1}'` -ne 6790 ]
then
echo `wc -c src/asm.h | awk '{print "Got " $1 ", Expected " 6790}'`
fi
if `test ! -s src/ops.c`
then
echo "writing src/ops.c"
cat > src/ops.c << '\Rogue\Monster\'
/*
* OPS.C
*
* (c)Copyright 1988, Matthew Dillon, All Rights Reserved.
*
* Handle mnemonics and pseudo ops
*
*/
#include "asm.h"
ubyte Gen[256];
ubyte OrgFill = DEFORGFILL;
short Glen;
extern void generate();
extern void genfill();
extern void pushif();
/*
* An opcode modifies the SEGMENT flags in the following ways:
*/
void
v_processor(str)
register char *str;
{
extern MNE Mne6502[];
extern MNE Mne6803[];
extern MNE MneHD6303[];
extern MNE Mne68705[];
extern MNE Mne68HC11[];
register short none = 1;
static int called;
if (called)
return;
called = 1;
if (strcmp(str,"6502") == 0) {
addhashtable(Mne6502);
MsbOrder = 0; /* lsb,msb */
Processor = 6502;
}
if (strcmp(str,"6803") == 0) {
addhashtable(Mne6803);
MsbOrder = 1; /* msb,lsb */
Processor = 6803;
}
if (strcmp(str,"HD6303") == 0 || strcmp(str, "hd6303") == 0) {
addhashtable(Mne6803);
addhashtable(MneHD6303);
MsbOrder = 1; /* msb,lsb */
Processor = 6303;
}
if (strcmp(str,"68705") == 0) {
addhashtable(Mne68705);
MsbOrder = 1; /* msb,lsb */
Processor = 68705;
}
if (strcmp(str,"68HC11") == 0 || strcmp(str, "68hc11") == 0) {
addhashtable(Mne68HC11);
MsbOrder = 1; /* msb,lsb */
Processor = 6811;
}
if (!Processor)
asmerr(20,1);
}
#define badcode(mne,adrmode) (!(mne->okmask & (1L << adrmode)))
void
v_mnemonic(str,mne)
register MNE *mne;
ubyte *str;
{
register uword addrmode;
register SYMBOL *sym;
register uword opcode;
short opidx;
SYMBOL *symbase;
short opsize;
Csegment->flags |= SF_REF;
programlabel();
symbase = eval(str);
if (Xtrace)
printf("PC: %04lx MNE: %s addrmode: %d ", Csegment->org, mne->name, symbase->addrmode);
for (sym = symbase; sym; sym = sym->next) {
if (sym->flags & SYM_UNKNOWN) {
++Redo;
Redo_why |= 1 << 0;
}
}
sym = symbase;
if (mne->flags & MF_IMOD) {
if (sym->next) {
sym->addrmode = AM_BITMOD;
if ((mne->flags & MF_REL) && sym->next)
sym->addrmode = AM_BITBRAMOD;
}
}
addrmode = sym->addrmode;
if ((sym->flags & SYM_UNKNOWN) || sym->value >= 0x100)
opsize = 2;
else
opsize = (sym->value) ? 1 : 0;
while (badcode(mne,addrmode) && Cvt[addrmode])
addrmode = Cvt[addrmode];
if (Xtrace)
printf("mnemask: %08lx adrmode: %d Cvt[am]: %d\n", mne->okmask, addrmode, Cvt[addrmode]);
if (badcode(mne,addrmode)) {
asmerr(5,0);
freesymbollist(symbase);
return;
}
if (Mnext >= 0 && Mnext < NUMOC) { /* Force */
addrmode = Mnext;
if (badcode(mne,addrmode)) {
asmerr(19,0);
freesymbollist(symbase);
return;
}
}
if (Xtrace)
printf("final addrmode = %d\n", addrmode);
while (opsize > Opsize[addrmode]) {
if (Cvt[addrmode] == 0 || badcode(mne,Cvt[addrmode])) {
if (sym->flags & SYM_UNKNOWN)
break;
asmerr(14,0);
break;
}
addrmode = Cvt[addrmode];
}
opcode = mne->opcode[addrmode];
opidx = 1 + (opcode > 0xFF);
if (opidx == 2) {
Gen[0] = opcode >> 8;
Gen[1] = opcode;
} else {
Gen[0] = opcode;
}
switch(addrmode) {
case AM_BITMOD:
sym = symbase->next;
if (!(sym->flags & SYM_UNKNOWN) && sym->value >= 0x100)
asmerr(14,0);
Gen[opidx++] = sym->value;
if (!(symbase->flags & SYM_UNKNOWN)) {
if (symbase->value > 7)
asmerr(15,0);
else
Gen[0] += symbase->value << 1;
}
break;
case AM_BITBRAMOD:
if (!(symbase->flags & SYM_UNKNOWN)) {
if (symbase->value > 7)
asmerr(15,0);
else
Gen[0] += symbase->value << 1;
}
sym = symbase->next;
if (!(sym->flags & SYM_UNKNOWN) && sym->value >= 0x100)
asmerr(14,0);
Gen[opidx++] = sym->value;
sym = sym->next;
break;
case AM_REL:
break;
default:
if (Opsize[addrmode] > 0)
Gen[opidx++] = sym->value;
if (Opsize[addrmode] == 2) {
if (MsbOrder) {
Gen[opidx-1] = sym->value >> 8;
Gen[opidx++] = sym->value;
} else {
Gen[opidx++] = sym->value >> 8;
}
}
sym = sym->next;
break;
}
if (mne->flags & MF_MASK) {
if (sym) {
if (!(sym->flags & SYM_UNKNOWN) && sym->value >= 0x100)
asmerr(14,0);
Gen[opidx] = sym->value;
sym = sym->next;
} else {
asmerr(16, 1);
}
++opidx;
}
if ((mne->flags & MF_REL) || addrmode == AM_REL) {
++opidx; /* to end of instruction */
if (!sym)
asmerr(16, 1);
else
if (!(sym->flags & SYM_UNKNOWN)) {
long pc;
ubyte pcf;
long dest;
pc = (Csegment->flags & SF_RORG) ? Csegment->rorg : Csegment->org;
pcf= (Csegment->flags & SF_RORG) ? Csegment->rflags : Csegment->flags;
if ((pcf & 3) == 0) {
dest = sym->value - pc - opidx;
if (dest >= 128 || dest < -128)
asmerr(10,0);
}
Gen[opidx-1] = dest & 0xFF; /* byte before end of inst. */
}
}
Glen = opidx;
generate();
freesymbollist(symbase);
}
v_trace(str)
char *str;
{
if (str[1] == 'n')
Xtrace = 1;
else
Xtrace = 0;
}
v_list(str)
char *str;
{
programlabel();
Glen = 0; /* Only so outlist() works */
if (strncmp(str, "off", 2) == 0 || strncmp(str, "OFF", 2) == 0)
ListMode = 0;
else
ListMode = 1;
}
v_include(str)
char *str;
{
char *buf;
programlabel();
if (*str == '\"') {
buf = (char *)malloc(strlen(str));
strcpy(buf, str+1);
for (str = buf; *str && *str != '\"'; ++str);
*str = 0;
pushinclude(buf);
free(buf);
} else {
pushinclude(str);
}
}
v_seg(str)
char *str;
{
register SEGMENT *seg;
for (seg = Seglist; seg; seg = seg->next) {
if (strcmp(str, seg->name) == 0) {
Csegment = seg;
programlabel();
return;
}
}
Csegment = seg = (SEGMENT *)zmalloc(sizeof(SEGMENT));
seg->next = Seglist;
seg->name = strcpy(malloc(strlen(str)+1), str);
seg->flags= seg->rflags = seg->initflags = seg->initrflags = SF_UNKNOWN;
Seglist = seg;
if (Mnext == AM_BSS)
seg->flags |= SF_BSS;
programlabel();
}
v_hex(str)
register char *str;
{
register int i;
register int result;
programlabel();
Glen = 0;
for (i = 0; str[i]; ++i) {
if (str[i] == ' ')
continue;
result = (gethexdig(str[i]) << 4) + gethexdig(str[i+1]);
if (str[++i] == 0)
break;
Gen[Glen++] = result;
}
generate();
}
gethexdig(c)
{
if (c >= '0' && c <= '9')
return(c - '0');
if (c >= 'a' && c <= 'f')
return(c - 'a' + 10);
if (c >= 'A' && c <= 'F')
return(c - 'A' + 10);
asmerr(0,0);
puts("(Must be a valid hex digit)");
if (F_listfile)
fputs("(Must be a valid hex digit)\n", FI_listfile);
return(0);
}
v_err()
{
programlabel();
asmerr(11, 1);
exit(1);
}
v_dc(str,mne)
char *str;
MNE *mne;
{
register SYMBOL *sym;
register SYMBOL *tmp;
register ulong value;
char *macstr;
char vmode = 0;
Glen = 0;
programlabel();
if (mne->name[1] == 'v') {
register short i;
vmode = 1;
for (i = 0; str[i] && str[i] != ' '; ++i);
tmp = findsymbol(str, i);
str += i;
if (tmp == NULL) {
puts("EQM label not found");
return;
}
if (tmp->flags & SYM_MACRO) {
macstr = (char *)tmp->string;
} else {
puts("must specify EQM label for DV");
return;
}
}
sym = eval(str);
for (; sym; sym = sym->next) {
value = sym->value;
if (sym->flags & SYM_UNKNOWN) {
++Redo;
Redo_why |= (1 << 2);
}
if (sym->flags & SYM_STRING) {
register ubyte *ptr = (ubyte *)sym->string;
while (value = *ptr) {
if (vmode) {
setspecial(value, 0);
tmp = eval(macstr);
value = tmp->value;
if (tmp->flags & SYM_UNKNOWN) {
++Redo;
Redo_why |= (1 << 3);
}
freesymbollist(tmp);
}
switch(Mnext) {
default:
case AM_BYTE:
Gen[Glen++] = value & 0xFF;
break;
case AM_WORD:
if (MsbOrder) {
Gen[Glen++] = (value >> 8) & 0xFF;
Gen[Glen++] = value & 0xFF;
} else {
Gen[Glen++] = value & 0xFF;
Gen[Glen++] = (value >> 8) & 0xFF;
}
break;
case AM_LONG:
if (MsbOrder) {
Gen[Glen++] = (value >> 24)& 0xFF;
Gen[Glen++] = (value >> 16)& 0xFF;
Gen[Glen++] = (value >> 8) & 0xFF;
Gen[Glen++] = value & 0xFF;
} else {
Gen[Glen++] = value & 0xFF;
Gen[Glen++] = (value >> 8) & 0xFF;
Gen[Glen++] = (value >> 16)& 0xFF;
Gen[Glen++] = (value >> 24)& 0xFF;
}
break;
}
++ptr;
}
} else {
if (vmode) {
setspecial(value, sym->flags);
tmp = eval(macstr);
value = tmp->value;
if (tmp->flags & SYM_UNKNOWN) {
++Redo;
Redo_why |= 1 << 4;
}
freesymbollist(tmp);
}
switch(Mnext) {
default:
case AM_BYTE:
Gen[Glen++] = value & 0xFF;
break;
case AM_WORD:
if (MsbOrder) {
Gen[Glen++] = (value >> 8) & 0xFF;
Gen[Glen++] = value & 0xFF;
} else {
Gen[Glen++] = value & 0xFF;
Gen[Glen++] = (value >> 8) & 0xFF;
}
break;
case AM_LONG:
if (MsbOrder) {
Gen[Glen++] = (value >> 24)& 0xFF;
Gen[Glen++] = (value >> 16)& 0xFF;
Gen[Glen++] = (value >> 8) & 0xFF;
Gen[Glen++] = value & 0xFF;
} else {
Gen[Glen++] = value & 0xFF;
Gen[Glen++] = (value >> 8) & 0xFF;
Gen[Glen++] = (value >> 16)& 0xFF;
Gen[Glen++] = (value >> 24)& 0xFF;
}
break;
}
}
}
generate();
freesymbollist(sym);
}
v_ds(str)
char *str;
{
register SYMBOL *sym;
int mult = 1;
long filler = 0;
if (Mnext == AM_WORD)
mult = 2;
if (Mnext == AM_LONG)
mult = 4;
programlabel();
if (sym = eval(str)) {
if (sym->next)
filler = sym->next->value;
if (sym->flags & SYM_UNKNOWN) {
++Redo;
Redo_why |= 1 << 5;
} else {
if (sym->next && sym->next->flags & SYM_UNKNOWN) {
++Redo;
Redo_why |= 1 << 5;
}
genfill(filler, sym->value, mult);
}
freesymbollist(sym);
}
}
v_org(str)
char *str;
{
register SYMBOL *sym;
sym = eval(str);
Csegment->org = sym->value;
if (sym->flags & SYM_UNKNOWN)
Csegment->flags |= SYM_UNKNOWN;
else
Csegment->flags &= ~SYM_UNKNOWN;
if (Csegment->initflags & SYM_UNKNOWN) {
Csegment->initorg = sym->value;
Csegment->initflags = sym->flags;
}
if (sym->next) {
OrgFill = sym->next->value;
if (sym->next->flags & SYM_UNKNOWN)
asmerr(18,1);
}
programlabel();
freesymbollist(sym);
}
v_rorg(str)
char *str;
{
register SYMBOL *sym = eval(str);
Csegment->flags |= SF_RORG;
if (sym->addrmode != AM_IMP) {
Csegment->rorg = sym->value;
if (sym->flags & SYM_UNKNOWN)
Csegment->rflags |= SYM_UNKNOWN;
else
Csegment->rflags &= ~SYM_UNKNOWN;
if (Csegment->initrflags & SYM_UNKNOWN) {
Csegment->initrorg = sym->value;
Csegment->initrflags = sym->flags;
}
}
programlabel();
freesymbollist(sym);
}
v_rend()
{
programlabel();
Csegment->flags &= ~SF_RORG;
}
v_align(str)
char *str;
{
SYMBOL *sym = eval(str);
ubyte fill = 0;
ubyte rorg = Csegment->flags & SF_RORG;
if (rorg)
Csegment->rflags |= SF_REF;
else
Csegment->flags |= SF_REF;
if (sym->next) {
if (sym->next->flags & SYM_UNKNOWN) {
++Redo;
Redo_why |= 1 << 6;
} else {
fill = sym->value;
}
}
if (rorg) {
if ((Csegment->rflags | sym->flags) & SYM_UNKNOWN) {
++Redo;
Redo_why |= 1 << 7;
} else {
register long n = sym->value - (Csegment->rorg % sym->value);
if (n != sym->value)
genfill(fill, n, 1);
}
} else {
if ((Csegment->flags | sym->flags) & SYM_UNKNOWN) {
++Redo;
Redo_why |= 1 << 8;
} else {
register long n = sym->value - (Csegment->org % sym->value);
if (n != sym->value)
genfill(fill, n, 1);
}
}
freesymbollist(sym);
programlabel();
}
v_subroutine()
{
++Lastlocalindex;
Localindex = Lastlocalindex;
programlabel();
}
v_equ(str)
char *str;
{
SYMBOL *sym = eval(str);
SYMBOL *lab;
lab = findsymbol(Av[0], strlen(Av[0]));
if (!lab)
lab = createsymbol(Av[0], strlen(Av[0]));
if (!(lab->flags & SYM_UNKNOWN)) {
if (sym->flags & SYM_UNKNOWN) {
++Redo;
Redo_why |= 1 << 9;
} else {
if (lab->value != sym->value) {
asmerr(13,0);
printf("old value: $%04lx new value: $%04lx\n", lab->value, sym->value);
++Redo;
Redo_why |= 1 << 10;
}
}
}
lab->value = sym->value;
lab->flags = sym->flags & (SYM_UNKNOWN|SYM_STRING);
lab->string = sym->string;
sym->flags &= ~(SYM_STRING|SYM_MACRO);
freesymbollist(sym);
}
v_eqm(str)
char *str;
{
register SYMBOL *lab;
register int len = strlen(Av[0]);
if (lab = findsymbol(Av[0], len)) {
if (lab->flags & SYM_STRING)
free(lab->string);
} else {
lab = createsymbol(Av[0], len);
}
lab->value = 0;
lab->flags = SYM_STRING | SYM_SET | SYM_MACRO;
lab->string = strcpy(malloc(strlen(str)+1), str);
}
v_echo(str)
char *str;
{
SYMBOL *sym = eval(str);
SYMBOL *s;
char buf[256];
for (s = sym; s; s = s->next) {
if (!(s->flags & SYM_UNKNOWN)) {
if (s->flags & (SYM_MACRO|SYM_STRING))
sprintf(buf,"%s", s->string);
else
sprintf(buf,"$%lx", s->value);
if (FI_listfile)
fprintf(FI_listfile, " %s", buf);
printf(" %s", buf);
}
}
puts("");
if (FI_listfile)
putc('\n', FI_listfile);
}
v_set(str)
char *str;
{
SYMBOL *sym = eval(str);
SYMBOL *lab;
lab = findsymbol(Av[0], strlen(Av[0]));
if (!lab)
lab = createsymbol(Av[0], strlen(Av[0]));
lab->value = sym->value;
lab->flags = sym->flags & (SYM_UNKNOWN|SYM_STRING);
lab->string = sym->string;
sym->flags &= ~(SYM_STRING|SYM_MACRO);
freesymbollist(sym);
}
v_execmac(str,mac)
char *str;
MACRO *mac;
{
register INCFILE *inc;
STRLIST *base;
register STRLIST **psl, *sl;
register char *s1, *s2;
programlabel();
if (Mlevel == MAXMACLEVEL) {
puts("infinite macro recursion");
return(0);
}
++Mlevel;
base = (STRLIST *)malloc(strlen(str)+5);
base->next = NULL;
strcpy(base->buf, str);
psl = &base->next;
while (*str && *str != '\n') {
s1 = str;
while (*str && *str != '\n' && *str != ',')
++str;
sl = (STRLIST *)malloc(5+(str-s1));
sl->next = NULL;
*psl = sl;
psl = &sl->next;
bmov(s1, sl->buf, (str-s1));
sl->buf[str-s1] = 0;
if (*str == ',')
++str;
while (*str == ' ')
++str;
}
inc = (INCFILE *)zmalloc(sizeof(INCFILE));
inc->next = Incfile;
inc->name = mac->name;
inc->fi = Incfile->fi; /* garbage */
inc->lineno = 0;
inc->flags = INF_MACRO;
inc->saveidx = Localindex;
inc->strlist = mac->strlist;
inc->args = base;
Incfile = inc;
++Lastlocalindex;
Localindex = Lastlocalindex;
}
void
v_end()
{
puts("END not implemented yet");
}
void
v_endm()
{
register INCFILE *inc = Incfile;
register STRLIST *args, *an;
programlabel();
if (inc->flags & INF_MACRO) {
--Mlevel;
for (args = inc->args; args; args = an) {
an = args->next;
free(args);
}
Localindex = inc->saveidx;
Incfile = inc->next;
free(inc);
return;
}
puts("not within a macro");
}
v_mexit()
{
v_endm();
}
v_ifconst(str)
char *str;
{
SYMBOL *sym;
programlabel();
sym = eval(str);
pushif(sym->flags == 0);
freesymbollist(sym);
}
v_ifnconst(str)
char *str;
{
SYMBOL *sym;
programlabel();
sym = eval(str);
pushif(sym->flags != 0);
freesymbollist(sym);
}
void
v_if(str)
char *str;
{
SYMBOL *sym;
if (!Ifstack->true || !Ifstack->acctrue) {
pushif(0);
return;
}
programlabel();
sym = eval(str);
if (sym->flags) {
++Redo;
Redo_why |= 1 << 11;
pushif(0);
Ifstack->acctrue = 0;
} else {
pushif((short)!!sym->value);
}
freesymbollist(sym);
}
v_else()
{
if (Ifstack->acctrue && !(Ifstack->flags & IFF_BASE)) {
programlabel();
Ifstack->true = !Ifstack->true;
}
}
v_endif()
{
IFSTACK *ifs = Ifstack;
if (!(ifs->flags & IFF_BASE)) {
if (ifs->acctrue)
programlabel();
if (ifs->file != Incfile) {
puts("too many endif's");
} else {
Ifstack = ifs->next;
free(ifs);
}
}
}
v_repeat(str)
char *str;
{
register REPLOOP *rp;
register SYMBOL *sym;
if (!Ifstack->true || !Ifstack->acctrue) {
pushif(0);
return;
}
programlabel();
sym = eval(str);
if (sym->value == 0) {
pushif(0);
freesymbollist(sym);
return;
}
rp = (REPLOOP *)zmalloc(sizeof(REPLOOP));
rp->next = Reploop;
rp->file = Incfile;
if (Incfile->flags & INF_MACRO)
rp->seek = (long)Incfile->strlist;
else
rp->seek = ftell(Incfile->fi);
rp->lineno = Incfile->lineno;
rp->count = sym->value;
if (rp->flags = sym->flags) {
++Redo;
Redo_why |= 1 << 12;
}
Reploop = rp;
freesymbollist(sym);
pushif(1);
}
void
v_repend()
{
if (!Ifstack->true || !Ifstack->acctrue) {
v_endif();
return;
}
if (Reploop && Reploop->file == Incfile) {
if (Reploop->flags == 0 && --Reploop->count) {
if (Incfile->flags & INF_MACRO)
Incfile->strlist = (STRLIST *)Reploop->seek;
else
fseek(Incfile->fi,Reploop->seek,0);
Incfile->lineno = Reploop->lineno;
} else {
rmnode(&Reploop, sizeof(REPLOOP));
v_endif();
}
return;
}
puts("no repeat");
}
static long Seglen;
static long Seekback;
void
generate()
{
long seekpos;
static ulong org;
short i;
if (!Redo) {
if (!(Csegment->flags & SF_BSS)) {
for (i = Glen - 1; i >= 0; --i)
CheckSum += Gen[i];
if (Fisclear) {
Fisclear = 0;
if (Csegment->flags & SF_UNKNOWN) {
++Redo;
Redo_why |= 1 << 1;
return;
}
org = Csegment->org;
if (F_format < 3) {
putc((short)(org & 0xFF), FI_temp);
putc((short)((org >> 8) & 0xFF), FI_temp);
if (F_format == 2) {
Seekback = ftell(FI_temp);
Seglen = 0;
putc(0, FI_temp);
putc(0, FI_temp);
}
}
}
switch(F_format) {
default:
case 3:
case 1:
if (Csegment->org < org) {
printf("segment: %s %s vs current org: %04lx\n", Csegment->name, sftos(Csegment->org, Csegment->flags), org);
asmerr(12, 1);
exit(1);
}
while (Csegment->org != org) {
putc(OrgFill, FI_temp);
++org;
}
fwrite(Gen, Glen, 1, FI_temp);
break;
case 2:
if (org != Csegment->org) {
org = Csegment->org;
seekpos = ftell(FI_temp);
fseek(FI_temp, Seekback, 0);
putc((short)(Seglen & 0xFF), FI_temp);
putc((short)((Seglen >> 8) & 0xFF), FI_temp);
fseek(FI_temp, seekpos, 0);
putc((short)(org & 0xFF), FI_temp);
putc((short)((org >> 8) & 0xFF), FI_temp);
Seekback = ftell(FI_temp);
Seglen = 0;
putc(0, FI_temp);
putc(0, FI_temp);
}
fwrite(Gen, Glen, 1, FI_temp);
Seglen += Glen;
}
org += Glen;
}
}
Csegment->org += Glen;
if (Csegment->flags & SF_RORG)
Csegment->rorg += Glen;
}
void
closegenerate()
{
if (!Redo) {
if (F_format == 2) {
fseek(FI_temp, Seekback, 0);
putc((short)(Seglen & 0xFF), FI_temp);
putc((short)((Seglen >> 8) & 0xFF), FI_temp);
fseek(FI_temp, 0L, 2);
}
}
}
void
genfill(fill, entries, size)
long fill, entries;
{
register long bytes = entries; /* multiplied later */
register short i;
register ubyte c3,c2,c1,c0;
if (!bytes)
return;
c3 = fill >> 24;
c2 = fill >> 16;
c1 = fill >> 8;
c0 = fill;
switch(size) {
case 1:
bset(Gen, sizeof(Gen), c0);
break;
case 2:
bytes <<= 1;
for (i = 0; i < sizeof(Gen); i += 2) {
if (MsbOrder) {
Gen[i+0] = c1;
Gen[i+1] = c0;
} else {
Gen[i+0] = c0;
Gen[i+1] = c1;
}
}
break;
case 4:
bytes <<= 2;
for (i = 0; i < sizeof(Gen); i += 4) {
if (MsbOrder) {
Gen[i+0] = c3;
Gen[i+1] = c2;
Gen[i+2] = c1;
Gen[i+3] = c0;
} else {
Gen[i+0] = c0;
Gen[i+1] = c1;
Gen[i+2] = c2;
Gen[i+3] = c3;
}
}
break;
}
for (Glen = sizeof(Gen); bytes > sizeof(Gen); bytes -= sizeof(Gen))
generate();
Glen = bytes;
generate();
}
void
pushif(bool)
{
register IFSTACK *ifs = (IFSTACK *)zmalloc(sizeof(IFSTACK));
ifs->next = Ifstack;
ifs->file = Incfile;
ifs->flags = 0;
ifs->true = bool;
ifs->acctrue = Ifstack->acctrue && Ifstack->true;
Ifstack = ifs;
}
\Rogue\Monster\
else
echo "will not over write src/ops.c"
fi
if [ `wc -c src/ops.c | awk '{printf $1}'` -ne 20291 ]
then
echo `wc -c src/ops.c | awk '{print "Got " $1 ", Expected " 20291}'`
fi
if `test ! -s src/mne6502.c`
then
echo "writing src/mne6502.c"
cat > src/mne6502.c << '\Rogue\Monster\'
/*
* MNE6502.C
*
* (c)Copyright 1988, Matthew Dillon, All Rights Reserved.
*
*/
#include "asm.h"
extern void v_mnemonic();
#define ASTD AF_BYTEADR|AF_BYTEADRX|AF_WORDADR|AF_WORDADRX|\
AF_WORDADRY|AF_INDBYTEX|AF_INDBYTEY
MNE Mne6502[] = {
NULL, v_mnemonic, "adc", 0, AF_IMM8|ASTD,
{ 0x69, 0x65, 0x75, 0x6D, 0x7D, 0x79, 0x61, 0x71 },
NULL, v_mnemonic, "and", 0, AF_IMM8|ASTD,
{ 0x29, 0x25, 0x35, 0x2D, 0x3D, 0x39, 0x21, 0x31 },
NULL, v_mnemonic, "asl", 0, AF_IMP|AF_BYTEADR|AF_BYTEADRX|AF_WORDADR|AF_WORDADRX,
{ 0x0A, 0x06, 0x16, 0x0E, 0x1E },
NULL, v_mnemonic, "bcc", 0, AF_REL, { 0x90 },
NULL, v_mnemonic, "bcs", 0, AF_REL, { 0xB0 },
NULL, v_mnemonic, "beq", 0, AF_REL, { 0xF0 },
NULL, v_mnemonic, "bit", 0, AF_BYTEADR|AF_WORDADR,
{ 0x24, 0x2C },
NULL, v_mnemonic, "bmi", 0, AF_REL, { 0x30 },
NULL, v_mnemonic, "bne", 0, AF_REL, { 0xD0 },
NULL, v_mnemonic, "bpl", 0, AF_REL, { 0x10 },
NULL, v_mnemonic, "brk", 0, AF_IMP, { 0x00 },
NULL, v_mnemonic, "bvc", 0, AF_REL, { 0x50 },
NULL, v_mnemonic, "bvs", 0, AF_REL, { 0x70 },
NULL, v_mnemonic, "clc", 0, AF_IMP, { 0x18 },
NULL, v_mnemonic, "cld", 0, AF_IMP, { 0xD8 },
NULL, v_mnemonic, "cli", 0, AF_IMP, { 0x58 },
NULL, v_mnemonic, "clv", 0, AF_IMP, { 0xB8 },
NULL, v_mnemonic, "cmp", 0, AF_IMM8|ASTD,
{ 0xC9, 0xC5, 0xD5, 0xCD, 0xDD, 0xD9, 0xC1, 0xD1 },
NULL, v_mnemonic, "cpx", 0, AF_IMM8|AF_BYTEADR|AF_WORDADR,
{ 0xE0, 0xE4, 0xEC },
NULL, v_mnemonic, "cpy", 0, AF_IMM8|AF_BYTEADR|AF_WORDADR,
{ 0xC0, 0xC4, 0xCC },
NULL, v_mnemonic, "dec", 0, AF_BYTEADR|AF_BYTEADRX|AF_WORDADR|AF_WORDADRX,
{ 0xC6, 0xD6, 0xCE, 0xDE },
NULL, v_mnemonic, "dex", 0, AF_IMP, { 0xCA },
NULL, v_mnemonic, "dey", 0, AF_IMP, { 0x88 },
NULL, v_mnemonic, "eor", 0, AF_IMM8|ASTD,
{ 0x49, 0x45, 0x55, 0x4D, 0x5D, 0x59, 0x41,0x51 },
NULL, v_mnemonic, "inc", 0, AF_BYTEADR|AF_BYTEADRX|AF_WORDADR|AF_WORDADRX,
{ 0xE6, 0xF6, 0xEE, 0xFE },
NULL, v_mnemonic, "inx", 0, AF_IMP, { 0xE8 },
NULL, v_mnemonic, "iny", 0, AF_IMP, { 0xC8 },
NULL, v_mnemonic, "jmp", 0, AF_WORDADR|AF_INDWORD,
{ 0x4C, 0x6C },
NULL, v_mnemonic, "jsr", 0, AF_WORDADR, { 0x20 },
NULL, v_mnemonic, "lda", 0, AF_IMM8|ASTD,
{ 0xA9, 0xA5, 0xB5, 0xAD, 0xBD, 0xB9, 0xA1, 0xB1 },
NULL, v_mnemonic, "ldx", 0, AF_IMM8|AF_BYTEADR|AF_BYTEADRY|AF_WORDADR|AF_WORDADRY,
{ 0xA2, 0xA6, 0xB6, 0xAE, 0xBE },
NULL, v_mnemonic, "ldy", 0, AF_IMM8|AF_BYTEADR|AF_BYTEADRX|AF_WORDADR|AF_WORDADRX,
{ 0xA0, 0xA4, 0xB4, 0xAC, 0xBC },
NULL, v_mnemonic, "lsr", 0, AF_IMP|AF_BYTEADR|AF_BYTEADRX|AF_WORDADR|AF_WORDADRX,
{ 0x4A, 0x46, 0x56, 0x4E, 0x5E },
NULL, v_mnemonic, "nop", 0, AF_IMP, { 0xEA },
NULL, v_mnemonic, "ora", 0, AF_IMM8|ASTD,
{ 0x09, 0x05, 0x15, 0x0D, 0x1D, 0x19, 0x01, 0x11 },
NULL, v_mnemonic, "pha", 0, AF_IMP, { 0x48 },
NULL, v_mnemonic, "php", 0, AF_IMP, { 0x08 },
NULL, v_mnemonic, "pla", 0, AF_IMP, { 0x68 },
NULL, v_mnemonic, "plp", 0, AF_IMP, { 0x28 },
NULL, v_mnemonic, "rol", 0, AF_IMP|AF_BYTEADR|AF_BYTEADRX|AF_WORDADR|AF_WORDADRX,
{ 0x2A, 0x26, 0x36, 0x2E, 0x3E },
NULL, v_mnemonic, "ror", 0, AF_IMP|AF_BYTEADR|AF_BYTEADRX|AF_WORDADR|AF_WORDADRX,
{ 0x6A, 0x66, 0x76, 0x6E, 0x7E },
NULL, v_mnemonic, "rti", 0, AF_IMP, { 0x40 },
NULL, v_mnemonic, "rts", 0, AF_IMP, { 0x60 },
NULL, v_mnemonic, "sbc", 0, AF_IMM8|ASTD,
{ 0xE9, 0xE5, 0xF5, 0xED, 0xFD, 0xF9, 0xE1, 0xF1 },
NULL, v_mnemonic, "sec", 0, AF_IMP, { 0x38 },
NULL, v_mnemonic, "sed", 0, AF_IMP, { 0xF8 },
NULL, v_mnemonic, "sei", 0, AF_IMP, { 0x78 },
NULL, v_mnemonic, "sta", 0, ASTD,
{ 0x85, 0x95, 0x8D, 0x9D, 0x99, 0x81, 0x91 },
NULL, v_mnemonic, "stx", 0, AF_BYTEADR|AF_BYTEADRY|AF_WORDADR,
{ 0x86, 0x96, 0x8E },
NULL, v_mnemonic, "sty", 0, AF_BYTEADR|AF_BYTEADRX|AF_WORDADR,
{ 0x84, 0x94, 0x8C },
NULL, v_mnemonic, "tax", 0, AF_IMP, { 0xAA },
NULL, v_mnemonic, "tay", 0, AF_IMP, { 0xA8 },
NULL, v_mnemonic, "tsx", 0, AF_IMP, { 0xBA },
NULL, v_mnemonic, "txa", 0, AF_IMP, { 0x8A },
NULL, v_mnemonic, "txs", 0, AF_IMP, { 0x9A },
NULL, v_mnemonic, "tya", 0, AF_IMP, { 0x98 },
NULL
};
\Rogue\Monster\
else
echo "will not over write src/mne6502.c"
fi
if [ `wc -c src/mne6502.c | awk '{printf $1}'` -ne 4254 ]
then
echo `wc -c src/mne6502.c | awk '{print "Got " $1 ", Expected " 4254}'`
fi
if `test ! -s src/mne6811.c`
then
echo "writing src/mne6811.c"
cat > src/mne6811.c << '\Rogue\Monster\'
/*
* MNE6811.C
*
* (c)Copyright 1988, Matthew Dillon, All Rights Reserved.
*
* 68HC11 processor
*
* addressing modes:
* AF_IMM8
* AF_IMM16
* AF_BYTEADR
* AF_WORDADR
* AF_BYTEADRX
* AF_BYTEADRY
* AF_IMP
* AF_REL
*
* flags:
* MF_MASK contains additional byte argument
* MF_REL contains additional relative argument
*/
#include "asm.h"
extern void v_mnemonic();
#define AF_STD (AF_BYTEADR|AF_BYTEADRX|AF_BYTEADRY|AF_WORDADR)
#define AF_STDI (AF_IMM8|AF_STD)
#define AF_STDD (AF_IMM16|AF_STD)
#define AF_ASL (AF_BYTEADRX|AF_BYTEADRY|AF_WORDADR)
#define AF_BCLR (AF_BYTEADR|AF_BYTEADRX|AF_BYTEADRY)
MNE Mne68HC11[] = {
NULL, v_mnemonic, "aba", 0, AF_IMP, { 0x1B },
NULL, v_mnemonic, "abx", 0, AF_IMP, { 0x3A },
NULL, v_mnemonic, "aby", 0, AF_IMP, { 0x183A },
NULL, v_mnemonic, "adca", 0, AF_STDI,{ 0x89, 0x99, 0xA9, 0x18A9, 0xB9 },
NULL, v_mnemonic, "adcb", 0, AF_STDI,{ 0xC9, 0xD9, 0xE9, 0x18E9, 0xF9 },
NULL, v_mnemonic, "adda", 0, AF_STDI,{ 0x8B, 0x9B, 0xAB, 0x18AB, 0xBB },
NULL, v_mnemonic, "addb", 0, AF_STDI,{ 0xCB, 0xDB, 0xEB, 0x18EB, 0xFB },
NULL, v_mnemonic, "addd", 0, AF_STDD,{ 0xC3, 0xD3, 0xE3, 0x18E3, 0xF3 },
NULL, v_mnemonic, "anda", 0, AF_STDI,{ 0x84, 0x94, 0xA4, 0x18A4, 0xB4 },
NULL, v_mnemonic, "andb", 0, AF_STDI,{ 0xC4, 0xD4, 0xE4, 0x18E4, 0xF4 },
NULL, v_mnemonic, "asla", 0, AF_IMP, { 0x48 },
NULL, v_mnemonic, "aslb", 0, AF_IMP, { 0x58 },
NULL, v_mnemonic, "asl", 0, AF_ASL, { 0x68, 0x1868, 0x78 },
NULL, v_mnemonic, "asld", 0, AF_IMP, { 0x05 },
NULL, v_mnemonic, "asra", 0, AF_IMP, { 0x47 },
NULL, v_mnemonic, "asrb", 0, AF_IMP, { 0x57 },
NULL, v_mnemonic, "asr", 0, AF_ASL, { 0x67, 0x1867, 0x77 },
/* no asrd */
NULL, v_mnemonic, "bcc", 0, AF_REL, { 0x24 },
NULL, v_mnemonic, "bclr", MF_MASK, AF_BCLR, { 0x15, 0x1D, 0x181D },
NULL, v_mnemonic, "bcs", 0, AF_REL, { 0x25 },
NULL, v_mnemonic, "beq", 0, AF_REL, { 0x27 },
NULL, v_mnemonic, "bge", 0, AF_REL, { 0x2C },
NULL, v_mnemonic, "bgt", 0, AF_REL, { 0x2E },
NULL, v_mnemonic, "bhi", 0, AF_REL, { 0x22 },
NULL, v_mnemonic, "bhs", 0, AF_REL, { 0x24 },
NULL, v_mnemonic, "bita", 0, AF_STDI,{ 0x85, 0x95, 0xA5, 0x18A5, 0xB5 },
NULL, v_mnemonic, "bitb", 0, AF_STDI,{ 0xC5, 0xD5, 0xE5, 0x18E5, 0xF5 },
NULL, v_mnemonic, "ble", 0, AF_REL, { 0x2F },
NULL, v_mnemonic, "blo", 0, AF_REL, { 0x25 },
NULL, v_mnemonic, "bls", 0, AF_REL, { 0x23 },
NULL, v_mnemonic, "blt", 0, AF_REL, { 0x2D },
NULL, v_mnemonic, "bmi", 0, AF_REL, { 0x2B },
NULL, v_mnemonic, "bne", 0, AF_REL, { 0x26 },
NULL, v_mnemonic, "bpl", 0, AF_REL, { 0x2A },
NULL, v_mnemonic, "bra", 0, AF_REL, { 0x20 },
NULL, v_mnemonic, "brclr", MF_MASK|MF_REL, AF_BCLR,{ 0x13, 0x1F, 0x181F },
NULL, v_mnemonic, "brn", 0, AF_REL, { 0x21 },
NULL, v_mnemonic, "brset", MF_MASK|MF_REL, AF_BCLR,{ 0x12, 0x1E, 0x181E },
NULL, v_mnemonic, "bset", MF_MASK, AF_BCLR, { 0x14, 0x1C, 0x181C },
NULL, v_mnemonic, "bsr", 0, AF_REL, { 0x8D },
NULL, v_mnemonic, "bvc", 0, AF_REL, { 0x28 },
NULL, v_mnemonic, "bvs", 0, AF_REL, { 0x29 },
NULL, v_mnemonic, "cba", 0, AF_IMP, { 0x11 },
NULL, v_mnemonic, "clc", 0, AF_IMP, { 0x0C },
NULL, v_mnemonic, "cli", 0, AF_IMP, { 0x0E },
NULL, v_mnemonic, "clra", 0, AF_IMP, { 0x4F },
NULL, v_mnemonic, "clrb", 0, AF_IMP, { 0x5F },
NULL, v_mnemonic, "clr", 0, AF_ASL, { 0x6F, 0x186F, 0x7F },
NULL, v_mnemonic, "clv", 0, AF_IMP, { 0x0A },
NULL, v_mnemonic, "cmpa", 0, AF_STDI,{ 0x81, 0x91, 0xA1, 0x18A1, 0xB1 },
NULL, v_mnemonic, "cmpb", 0, AF_STDI,{ 0xC1, 0xD1, 0xE1, 0x18E1, 0xF1 },
NULL, v_mnemonic, "coma", 0, AF_IMP, { 0x43 },
NULL, v_mnemonic, "comb", 0, AF_IMP, { 0x53 },
NULL, v_mnemonic, "com", 0, AF_ASL, { 0x63, 0x1863, 0x73 },
NULL, v_mnemonic, "cpd", 0, AF_STDD,{ 0x1A83, 0x1A93, 0x1AA3, 0xCDA3, 0x1AB3 },
NULL, v_mnemonic, "cpx", 0, AF_STDD,{ 0x8C, 0x9C, 0xAC, 0xCDAC, 0xBC },
NULL, v_mnemonic, "cpy", 0, AF_STDD,{ 0x188C, 0x189C, 0x1AAC, 0x18AC, 0x18BC },
NULL, v_mnemonic, "daa", 0, AF_IMP, { 0x19 },
NULL, v_mnemonic, "deca", 0, AF_IMP, { 0x4A },
NULL, v_mnemonic, "decb", 0, AF_IMP, { 0x5A },
NULL, v_mnemonic, "dec", 0, AF_ASL, { 0x6A, 0x186A, 0x7A },
NULL, v_mnemonic, "des", 0, AF_IMP, { 0x34 },
NULL, v_mnemonic, "dex", 0, AF_IMP, { 0x09 },
NULL, v_mnemonic, "dey", 0, AF_IMP, { 0x1809 },
NULL, v_mnemonic, "eora", 0, AF_STDI,{ 0x88, 0x98, 0xA8, 0x18A8, 0xB8 },
NULL, v_mnemonic, "eorb", 0, AF_STDI,{ 0xC8, 0xD8, 0xE8, 0x18E8, 0xF8 },
NULL, v_mnemonic, "fdiv", 0, AF_IMP, { 0x03 },
NULL, v_mnemonic, "idiv", 0, AF_IMP, { 0x02 },
NULL, v_mnemonic, "inca", 0, AF_IMP, { 0x4C },
NULL, v_mnemonic, "incb", 0, AF_IMP, { 0x5C },
NULL, v_mnemonic, "inc", 0, AF_ASL, { 0x6C, 0x186C, 0x7C },
NULL, v_mnemonic, "ins", 0, AF_IMP, { 0x31 },
NULL, v_mnemonic, "inx", 0, AF_IMP, { 0x08 },
NULL, v_mnemonic, "iny", 0, AF_IMP, { 0x1808 },
NULL, v_mnemonic, "jmp", 0, AF_ASL, { 0x6E, 0x186E, 0x7E },
NULL, v_mnemonic, "jsr", 0, AF_STD, { 0x9D, 0xAD, 0x18AD, 0xBD },
NULL, v_mnemonic, "ldaa", 0, AF_STDI,{ 0x86, 0x96, 0xA6, 0x18A6, 0xB6 },
NULL, v_mnemonic, "ldab", 0, AF_STDI,{ 0xC6, 0xD6, 0xE6, 0x18E6, 0xF6 },
NULL, v_mnemonic, "ldd", 0, AF_STDD,{ 0xCC, 0xDC, 0xEC, 0x18EC, 0xFC },
NULL, v_mnemonic, "lds", 0, AF_STDD,{ 0x8E, 0x9E, 0xAE, 0x18AE, 0xBE },
NULL, v_mnemonic, "ldx", 0, AF_STDD,{ 0xCE, 0xDE, 0xEE, 0xCDEE, 0xFE },
NULL, v_mnemonic, "ldy", 0, AF_STDD,{ 0x18CE, 0x18DE, 0x1AEE, 0x18EE, 0x18FE },
NULL, v_mnemonic, "lsla", 0, AF_IMP, { 0x48 },
NULL, v_mnemonic, "lslb", 0, AF_IMP, { 0x58 },
NULL, v_mnemonic, "lsl", 0, AF_ASL, { 0x68, 0x1868, 0x78 },
NULL, v_mnemonic, "lsld", 0, AF_IMP, { 0x05 },
NULL, v_mnemonic, "lsra", 0, AF_IMP, { 0x44 },
NULL, v_mnemonic, "lsrb", 0, AF_IMP, { 0x54 },
NULL, v_mnemonic, "lsr", 0, AF_ASL, { 0x64, 0x1864, 0x74 },
NULL, v_mnemonic, "lsrd", 0, AF_IMP, { 0x04 },
NULL, v_mnemonic, "mul", 0, AF_IMP, { 0x3D },
NULL, v_mnemonic, "nega", 0, AF_IMP, { 0x40 },
NULL, v_mnemonic, "negb", 0, AF_IMP, { 0x50 },
NULL, v_mnemonic, "neg", 0, AF_ASL, { 0x60, 0x1860, 0x70 },
NULL, v_mnemonic, "nop", 0, AF_IMP, { 0x01 },
NULL, v_mnemonic, "oraa", 0, AF_STDI,{ 0x8A, 0x9A, 0xAA, 0x18AA, 0xBA },
NULL, v_mnemonic, "orab", 0, AF_STDI,{ 0xCA, 0xDA, 0xEA, 0x18EA, 0xFA },
NULL, v_mnemonic, "psha", 0, AF_IMP, { 0x36 },
NULL, v_mnemonic, "pshb", 0, AF_IMP, { 0x37 },
NULL, v_mnemonic, "pshx", 0, AF_IMP, { 0x3C },
NULL, v_mnemonic, "pshy", 0, AF_IMP, { 0x183C },
NULL, v_mnemonic, "pula", 0, AF_IMP, { 0x32 },
NULL, v_mnemonic, "pulb", 0, AF_IMP, { 0x33 },
NULL, v_mnemonic, "pulx", 0, AF_IMP, { 0x38 },
NULL, v_mnemonic, "puly", 0, AF_IMP, { 0x1838 },
NULL, v_mnemonic, "rola", 0, AF_IMP, { 0x49 },
NULL, v_mnemonic, "rolb", 0, AF_IMP, { 0x59 },
NULL, v_mnemonic, "rol", 0, AF_ASL, { 0x69, 0x1869, 0x79 },
NULL, v_mnemonic, "rora", 0, AF_IMP, { 0x46 },
NULL, v_mnemonic, "rorb", 0, AF_IMP, { 0x56 },
NULL, v_mnemonic, "ror", 0, AF_ASL, { 0x66, 0x1866, 0x76 },
NULL, v_mnemonic, "rti", 0, AF_IMP, { 0x3B },
NULL, v_mnemonic, "rts", 0, AF_IMP, { 0x39 },
NULL, v_mnemonic, "sba", 0, AF_IMP, { 0x10 },
NULL, v_mnemonic, "sbca", 0, AF_STDI,{ 0x82, 0x92, 0xA2, 0x18A2, 0xB2 },
NULL, v_mnemonic, "sbcb", 0, AF_STDI,{ 0xC2, 0xD2, 0xE2, 0x18E2, 0xF2 },
NULL, v_mnemonic, "sec", 0, AF_IMP, { 0x0D },
NULL, v_mnemonic, "sei", 0, AF_IMP, { 0x0F },
NULL, v_mnemonic, "sev", 0, AF_IMP, { 0x0B },
NULL, v_mnemonic, "staa", 0, AF_STD, { 0x97, 0xA7, 0x18A7, 0xB7 },
NULL, v_mnemonic, "stab", 0, AF_STD, { 0xD7, 0xE7, 0x18E7, 0xF7 },
NULL, v_mnemonic, "std", 0, AF_STD, { 0xDD, 0xED, 0x18ED, 0xFD },
NULL, v_mnemonic, "stop", 0, AF_IMP, { 0xCF },
NULL, v_mnemonic, "sts", 0, AF_STD, { 0x9F, 0xAF, 0x18AF, 0xBF },
NULL, v_mnemonic, "stx", 0, AF_STD, { 0xDF, 0xEF, 0xCDEF, 0xFF },
NULL, v_mnemonic, "sty", 0, AF_STD, { 0x18DF, 0x1AEF, 0x18EF, 0x18FF },
NULL, v_mnemonic, "suba", 0, AF_STDI,{ 0x80, 0x90, 0xA0, 0x18A0, 0xB0 },
NULL, v_mnemonic, "subb", 0, AF_STDI,{ 0xC0, 0xD0, 0xE0, 0x18E0, 0xF0 },
NULL, v_mnemonic, "subd", 0, AF_STDD,{ 0x83, 0x93, 0xA3, 0x18A3, 0xB3 },
NULL, v_mnemonic, "swi", 0, AF_IMP, { 0x3F },
NULL, v_mnemonic, "tab", 0, AF_IMP, { 0x16 },
NULL, v_mnemonic, "tap", 0, AF_IMP, { 0x06 },
NULL, v_mnemonic, "tba", 0, AF_IMP, { 0x17 },
NULL, v_mnemonic, "test", 0, AF_IMP, { 0x00 },
NULL, v_mnemonic, "tpa", 0, AF_IMP, { 0x07 },
NULL, v_mnemonic, "tsta", 0, AF_IMP, { 0x4D },
NULL, v_mnemonic, "tstb", 0, AF_IMP, { 0x5D },
NULL, v_mnemonic, "tst", 0, AF_ASL, { 0x6D, 0x186D, 0x7D },
NULL, v_mnemonic, "tsx", 0, AF_IMP, { 0x30 },
NULL, v_mnemonic, "tsy", 0, AF_IMP, { 0x1830 },
NULL, v_mnemonic, "txs", 0, AF_IMP, { 0x35 },
NULL, v_mnemonic, "tys", 0, AF_IMP, { 0x1835 },
NULL, v_mnemonic, "wai", 0, AF_IMP, { 0x3E },
NULL, v_mnemonic, "xgdx", 0, AF_IMP, { 0x8F },
NULL, v_mnemonic, "xgdy", 0, AF_IMP, { 0x188F },
NULL
};
\Rogue\Monster\
else
echo "will not over write src/mne6811.c"
fi
if [ `wc -c src/mne6811.c | awk '{printf $1}'` -ne 9593 ]
then
echo `wc -c src/mne6811.c | awk '{print "Got " $1 ", Expected " 9593}'`
fi
if `test ! -s src/main.c`
then
echo "writing src/main.c"
cat > src/main.c << '\Rogue\Monster\'
/*
* MAIN.C
*
* (c)Copyright 1988, Matthew Dillon, All Rights Reserved.
* Freely Distributable (for non-profit) ONLY. No redistribution
* of any modified text files or redistribution of a subset of the
* source is allowed. Redistribution of modified binaries IS allowed
* under the above terms.
*
* DASM sourcefile
*
* NOTE: must handle mnemonic extensions and expression decode/compare.
*/
#include "asm.h"
#define MAXLINE 256
#define ISEGNAME "code"
extern uword hash1();
extern MNE *findmne();
extern MNE Ops[];
extern void findext();
extern void clearsegs(), clearrefs();
extern SYMBOL *eval();
extern char *cleanup();
uword _fmode = 0; /* was trying to port to 16 bit IBM-PC lattice C */
/* but failed */
ubyte Disable_me;
ubyte StopAtEnd = 0;
ubyte *Extstr;
main(ac, av)
ubyte *av[];
{
ubyte buf[MAXLINE];
uword pass, i;
register ubyte *ptr;
register MNE *mne;
register ulong oldredo = -1;
register ulong oldwhy = 0;
register ulong oldeval = 0;
addhashtable(Ops);
pass = 1;
if (ac < 2) {
fail:
puts("DASM V2.11, high level Macro Assembler");
puts("(C)Copyright 1988 by Matthew Dillon, All Rights Reserved");
puts("redistributable for non-profit only");
puts("");
puts("DASM sourcefile [options]");
puts(" -f# output format");
puts(" -oname output file");
puts(" -lname list file");
puts(" -sname symbol dump");
puts(" -v# verboseness");
puts(" -Dname=exp define label");
exit(1);
}
puts("DASM V2.11, (c)Copyright 1988 Matthew Dillon, All Rights Reserved");
puts("Warning: The meaning of <exp & >exp has been reversed in this release");
for (i = 2; i < ac; ++i) {
if (av[i][0] == '-') {
register ubyte *str = av[i]+2;
switch(av[i][1]) {
case 'd':
Xdebug = atoi(str);
printf("Xdebug = %ld\n", Xdebug);
break;
case 'D':
while (*str && *str != '=')
++str;
if (*str == '=') {
*str = 0;
++str;
} else {
str = (ubyte *)"0";
}
Av[0] = av[i]+2;
v_set(str);
break;
case 'f': /* F_format */
F_format = atoi(str);
if (F_format < 1 || F_format > 3)
panic("Illegal format specification");
break;
case 'o': /* F_outfile */
F_outfile = (char *)str;
nofile:
if (*str == 0)
panic("need file name for specified option");
break;
case 'l': /* F_listfile */
F_listfile = (char *)str;
goto nofile;
case 's': /* F_symfile */
F_symfile = (char *)str;
goto nofile;
case 'v': /* F_verbose */
F_verbose = atoi(str);
break;
case 't': /* F_temppath */
F_temppath = (char *)str;
break;
default:
goto fail;
}
continue;
}
goto fail;
}
/* INITIAL SEGMENT */
{
register SEGMENT *seg = (SEGMENT *)permalloc(sizeof(SEGMENT));
seg->name = strcpy(permalloc(sizeof(ISEGNAME)), ISEGNAME);
seg->flags= seg->rflags = seg->initflags = seg->initrflags = SF_UNKNOWN;
Csegment = Seglist = seg;
}
/* TOP LEVEL IF */
{
register IFSTACK *ifs = (IFSTACK *)zmalloc(sizeof(IFSTACK));
ifs->file = NULL;
ifs->flags = IFF_BASE;
ifs->acctrue = 1;
ifs->true = 1;
Ifstack = ifs;
}
nextpass:
Localindex = Lastlocalindex = 0;
_fmode = 0x8000;
FI_temp = fopen(F_outfile, "w");
_fmode = 0;
Fisclear = 1;
CheckSum = 0;
if (FI_temp == NULL) {
printf("unable to [re]open '%s'\n", F_outfile);
exit(1);
}
if (F_listfile) {
FI_listfile = fopen(F_listfile, "w");
if (FI_listfile == NULL) {
printf("unable to [re]open '%s'\n", F_listfile);
exit(1);
}
}
pushinclude(av[1]);
while (Incfile) {
for (;;) {
char *comment;
if (Incfile->flags & INF_MACRO) {
if (Incfile->strlist == NULL) {
Av[0] = (ubyte *)"";
v_mexit();
continue;
}
strcpy(buf, Incfile->strlist->buf);
Incfile->strlist = Incfile->strlist->next;
} else {
if (fgets(buf, MAXLINE, Incfile->fi) == NULL)
break;
}
if (Xdebug)
printf("%08lx %s\n", Incfile, buf);
comment = cleanup(buf);
if (Xdebug)
printf("ok1 "), fflush(stdout);
++Incfile->lineno;
parse(buf);
if (Xdebug)
printf("ok2 "), fflush(stdout);
if (Av[1][0]) {
findext(Av[1]);
if (mne = findmne(Av[1])) {
if ((mne->flags & MF_IF) || (Ifstack->true && Ifstack->acctrue))
(*mne->vect)(Av[2], mne);
} else {
if (Ifstack->true && Ifstack->acctrue) {
printf("unknown mnemonic: '%s'\n", Av[1]);
asmerr(4,0);
}
}
} else {
if (Ifstack->true && Ifstack->acctrue)
programlabel();
}
if (Xdebug)
printf("ok3 "), fflush(stdout);
if (F_listfile && ListMode)
outlistfile(comment);
}
while (Reploop && Reploop->file == Incfile)
rmnode(&Reploop, sizeof(REPLOOP));
while (Ifstack->file == Incfile)
rmnode(&Ifstack, sizeof(IFSTACK));
fclose(Incfile->fi);
free(Incfile->name);
--Inclevel;
rmnode(&Incfile, sizeof(INCFILE));
if (Incfile) {
/*
if (F_verbose > 1)
printf("back to: %s\n", Incfile->name);
*/
if (F_listfile)
fprintf(FI_listfile, "------- FILE %s\n", Incfile->name);
}
}
if (F_verbose >= 1) {
SEGMENT *seg;
char *bss;
puts("");
printf("END OF PASS: %d\n", pass);
puts("Segment--- init-pc init-rpc finl-pc finl-rpc");
for (seg = Seglist; seg; seg = seg->next) {
bss = (seg->flags & SF_BSS) ? "[u]" : " ";
printf("%10s %3s ", seg->name, bss);
printf("%s %s ", sftos(seg->initorg, seg->initflags), sftos(seg->initrorg, seg->initrflags));
printf("%s %s\n", sftos(seg->org, seg->flags), sftos(seg->rorg, seg->rflags));
}
printf("Reasons: %4ld,%4ld Reasoncode: %08lx\n", Redo, Redo_eval, Redo_why);
}
if (F_verbose >= 3) {
SYMBOL *sym;
short i;
short j = 0;
if (F_verbose == 3)
puts("SYMBOLIST: (Unresolved symbols only)");
else
puts("SYMBOLIST");
for (i = 0; i < SHASHSIZE; ++i) {
for (sym = SHash[i]; sym; sym = sym->next) {
if (F_verbose > 3 || (sym->flags & SYM_UNKNOWN)) {
printf("%10s %s\n", sym->name, sftos(sym->value, sym->flags));
j = 1;
}
}
}
if (j == 0)
puts("NO SYMBOLS");
else
puts("ENDSYMBOLIST");
}
closegenerate();
fclose(FI_temp);
if (FI_listfile)
fclose(FI_listfile);
if (Redo) {
if (Redo == oldredo && Redo_why == oldwhy && Redo_eval == oldeval) {
puts("Error: source is not resolvable.");
if (F_verbose < 2)
puts("re-run with verbose option 2 or higher to determine problem");
exit(1);
}
oldredo = Redo;
oldwhy = Redo_why;
oldeval = Redo_eval;
Redo = 0;
Redo_why = 0;
Redo_eval = 0;
++pass;
if (StopAtEnd) {
printf("Unrecoverable error in pass, aborting assembly!\n");
} else if (pass > 10) {
printf("More than 10 passes, something *must* be wrong!\n");
exit(1);
} else {
clearrefs();
clearsegs();
goto nextpass;
}
}
if (F_symfile) {
FILE *fi = fopen(F_symfile, "w");
if (fi) {
register SYMBOL *sym;
puts("dumping symbols...");
for (i = 0; i < SHASHSIZE; ++i) {
for (sym = SHash[i]; sym; sym = sym->next) {
fprintf(fi, "%-15s %s", sym->name, sftos(sym->value, sym->flags));
if (sym->flags & SYM_STRING)
fprintf(fi, " \"%s\"", sym->string);
putc('\n', fi);
}
}
fclose(fi);
} else {
printf("unable to open symbol dump file '%s'\n", F_symfile);
}
}
}
static
outlistfile(comment)
char *comment;
{
extern ubyte Gen[];
extern short Glen;
char c = (Pflags & SF_BSS) ? 'U' : ' ';
static char buf1[MAXLINE+32];
static char buf2[MAXLINE+32];
ubyte *ptr = Extstr;
char *dot = "";
register int i, j;
if (ptr)
dot = ".";
else
ptr = (ubyte *)"";
sprintf(buf1, "%6ld %c%s", Incfile->lineno, c, sftos(Plab, Pflags & 7));
j = strlen(buf1);
for (i = 0; i < Glen && i < 4; ++i, j += 3)
sprintf(buf1+j, "%02x ", Gen[i]);
if (i < Glen && i == 4)
buf1[j-1] = '*';
for (; i < 4; ++i) {
buf1[j] = buf1[j+1] = buf1[j+2] = ' ';
j += 3;
}
sprintf(buf1+j, "%-10s %s%s%s\011%s\n", Av[0], Av[1], dot, ptr, Av[2]);
if (comment[0]) { /* tab and comment */
j = strlen(buf1) - 1;
sprintf(buf1+j, "\011;%s", comment);
}
fwrite(buf2, tabit(buf1,buf2), 1, FI_listfile);
Glen = 0;
Extstr = NULL;
}
tabit(buf1, buf2)
char *buf1, *buf2;
{
register char *bp, *ptr;
register short j, k;
bp = buf2;
ptr= buf1;
for (j = 0; *ptr; ++ptr, ++bp, j = (j+1)&7) {
*bp = *ptr;
if (*ptr == 9)
j = 0;
if (j == 7 && *bp == ' ' && *(bp-1) == ' ') {
k = j;
while (k-- >= 0 && *bp == ' ')
--bp;
*++bp = 9;
}
}
while (bp != buf2 && bp[-1] == ' ' || bp[-1] == 9)
--bp;
*bp = *ptr;
return((int)(bp - buf2));
}
ubyte *
sftos(val, flags)
long val;
short flags;
{
static char buf[64];
static char c;
register char *ptr = (c) ? buf : buf + 32;
c = 1 - c;
sprintf(ptr, "%04lx", val);
if (flags & SYM_UNKNOWN)
strcpy(ptr, "????");
if (flags & SYM_STRING)
strcpy(ptr, "str ");
if (flags & SYM_MACRO)
strcpy(ptr, "eqm ");
strcpy(ptr+4, " ");
if (flags & (SYM_MASREF|SYM_SET)) {
ptr[4] = '(';
ptr[7] = ')';
}
if (flags & (SYM_MASREF))
ptr[5] = 'r';
if (flags & (SYM_SET))
ptr[6] = 's';
return((ubyte *)ptr);
}
void
clearsegs()
{
register SEGMENT *seg;
for (seg = Seglist; seg; seg = seg->next) {
seg->flags = (seg->flags & SF_BSS) | SF_UNKNOWN;
seg->rflags= seg->initflags = seg->initrflags = SF_UNKNOWN;
}
}
void
clearrefs()
{
register SYMBOL *sym;
register short i;
for (i = 0; i < SHASHSIZE; ++i)
for (sym = SHash[i]; sym; sym = sym->next)
sym->flags &= ~SYM_REF;
}
static
char *
cleanup(buf)
register ubyte *buf;
{
register ubyte *str;
register STRLIST *strlist;
register short arg, add;
char *comment = "";
for (str = buf; *str; ++str) {
switch(*str) {
case ';':
comment = (char *)str + 1;
/* FALL THROUGH */
case '\r':
case '\n':
goto br2;
case TAB:
*str = ' ';
break;
case '\'':
++str;
if (*str == TAB)
*str = ' ';
if (*str == '\n' || *str == 0) {
str[0] = ' ';
str[1] = 0;
}
if (str[0] == ' ')
str[0] = 0x80;
break;
case '\"':
++str;
while (*str && *str != '\"') {
if (*str == ' ')
*str = 0x80;
++str;
}
if (*str != '\"') {
asmerr(0,0);
--str;
}
break;
case '{':
if (Disable_me)
break;
if (Xdebug)
printf("macro tail: '%s'\n", str);
arg = atoi(str+1);
for (add = 0; *str && *str != '}'; ++str)
--add;
if (*str != '}') {
puts("end brace required");
--str;
break;
}
--add;
++str;
if (Xdebug)
printf("add/str: %d '%s'\n", add, str);
for (strlist = Incfile->args; arg && strlist;) {
--arg;
strlist = strlist->next;
}
if (strlist) {
add += strlen(strlist->buf);
if (Xdebug)
printf("strlist: '%s' %d\n", strlist->buf, strlen(strlist->buf));
if (str + add + strlen(str) + 1 > buf + MAXLINE) {
if (Xdebug)
printf("str %8ld buf %8ld (add/strlen(str)): %d %ld\n", str, buf, add, strlen(str));
panic("failure1");
}
bmov(str, str + add, strlen(str)+1);
str += add;
if (str - strlen(strlist->buf) < buf)
panic("failure2");
bmov(strlist->buf, str - strlen(strlist->buf), strlen(strlist->buf));
str -= strlen(strlist->buf);
if (str < buf || str >= buf + MAXLINE)
panic("failure 3");
--str; /* for loop increments string */
} else {
asmerr(7,0);
goto br2;
}
break;
}
}
br2:
while(str != buf && *(str-1) == ' ')
--str;
*str = 0;
return(comment);
}
panic(str)
char *str;
{
puts(str);
exit(1);
}
/*
* .dir direct x
* .ext extended x
* .r relative x
* .x index, no offset x
* .x8 index, byte offset x
* .x16 index, word offset x
* .bit bit set/clr
* .bbr bit and branch
* .imp implied (inherent) x
* .b x
* .w x
* .l x
* .u x
*/
void
findext(str)
register ubyte *str;
{
Mnext = -1;
Extstr = NULL;
while (*str && *str != '.')
++str;
if (*str) {
*str = 0;
++str;
Extstr = str;
switch(str[0]|0x20) {
case '0':
case 'i':
Mnext = AM_IMP;
switch(str[1]|0x20) {
case 'x':
Mnext = AM_0X;
break;
case 'y':
Mnext = AM_0Y;
break;
case 'n':
Mnext = AM_INDWORD;
break;
}
return;
case 'd':
case 'b':
case 'z':
switch(str[1]|0x20) {
case 'x':
Mnext = AM_BYTEADRX;
break;
case 'y':
Mnext = AM_BYTEADRY;
break;
case 'i':
Mnext = AM_BITMOD;
break;
case 'b':
Mnext = AM_BITBRAMOD;
break;
default:
Mnext = AM_BYTEADR;
break;
}
return;
case 'e':
case 'w':
case 'a':
switch(str[1]|0x20) {
case 'x':
Mnext = AM_WORDADRX;
break;
case 'y':
Mnext = AM_WORDADRY;
break;
default:
Mnext = AM_WORDADR;
break;
}
return;
case 'l':
Mnext = AM_LONG;
return;
case 'r':
Mnext = AM_REL;
return;
case 'u':
Mnext = AM_BSS;
return;
}
}
}
/*
* bytes arg will eventually be used to implement a linked list of free
* nodes.
*/
rmnode(base, bytes)
ulong **base;
{
ulong *node;
if (node = *base) {
*base = *(ulong **)node;
free(node);
}
}
/*
* Parse into three arguments: Av[0], Av[1], Av[2]
*/
parse(buf)
register ubyte *buf;
{
register short i, j;
i = j = 0;
Av[0] = Avbuf;
while (buf[i] && buf[i] != ' ') {
if (buf[i] == 0x80)
buf[i] = ' ';
Avbuf[j++] = buf[i++];
}
Avbuf[j++] = 0;
while (buf[i] == ' ')
++i;
Av[1] = Avbuf + j;
while (buf[i] && buf[i] != ' ') {
if (buf[i] == 0x80)
buf[i] = ' ';
Avbuf[j++] = buf[i++];
}
Avbuf[j++] = 0;
while (buf[i] == ' ')
++i;
Av[2] = Avbuf + j;
while (buf[i]) {
if (buf[i] == ' ') {
while(buf[i+1] == ' ')
++i;
}
if (buf[i] == 0x80)
buf[i] = ' ';
Avbuf[j++] = buf[i++];
}
Avbuf[j] = 0;
}
MNE *
findmne(str)
register ubyte *str;
{
register uword i;
register ubyte c;
register MNE *mne;
ubyte buf[128];
for (i = 0; c = str[i]; ++i) {
if (c >= 'A' && c <= 'Z')
c += 'a' - 'A';
buf[i] = c;
}
buf[i] = 0;
for (mne = MHash[hash1(buf)]; mne; mne = mne->next) {
if (strcmp(buf, mne->name) == 0)
break;
}
return(mne);
}
v_macro(str)
char *str;
{
extern void v_execmac();
extern void v_endm();
STRLIST *base;
ubyte defined = 0;
register STRLIST **slp, *sl;
register MACRO *mac;
register MNE *mne;
register uword i;
ubyte buf[MAXLINE];
ubyte skipit = !(Ifstack->true && Ifstack->acctrue);
if (skipit) {
defined = 1;
} else {
defined = (findmne(str) != NULL);
if (F_listfile && ListMode)
outlistfile("");
}
if (!defined) {
base = NULL;
slp = &base;
mac = (MACRO *)permalloc(sizeof(MACRO));
i = hash1(str);
mac->next = (MACRO *)MHash[i];
mac->vect = v_execmac;
mac->name = strcpy(permalloc(strlen(str)+1), str);
mac->flags = MF_MACRO;
MHash[i] = (MNE *)mac;
}
while (fgets(buf, MAXLINE, Incfile->fi)) {
char *comment;
if (Xdebug)
printf("%08lx %s\n", Incfile, buf);
++Incfile->lineno;
Disable_me = 1;
comment = cleanup(buf);
Disable_me = 0;
if (parse(buf), Av[1][0]) {
findext(Av[1]);
mne = findmne(Av[1]);
if (mne->vect == v_endm) {
if (!defined)
mac->strlist = base;
return;
}
}
if (Xdebug)
printf("ok1"), fflush(stdout);
if (!skipit && F_listfile && ListMode)
outlistfile(comment);
if (Xdebug)
printf("ok2"), fflush(stdout);
if (!defined) {
sl = (STRLIST *)permalloc(5+strlen(buf));
strcpy(sl->buf, buf);
*slp = sl;
slp = &sl->next;
}
if (Xdebug)
printf("ok3\n"), fflush(stdout);
}
asmerr(8,1);
}
addhashtable(mne)
MNE *mne;
{
register uword i, j;
uword opcode[NUMOC];
for (; mne->vect; ++mne) {
bmov(mne->opcode, opcode, sizeof(mne->opcode));
for (i = j = 0; i < NUMOC; ++i) {
mne->opcode[i] = 0; /* not really needed */
if (mne->okmask & (1L << i))
mne->opcode[i] = opcode[j++];
}
i = hash1(mne->name);
mne->next = MHash[i];
MHash[i] = mne;
}
}
static uword
hash1(str)
register ubyte *str;
{
register uword result = 0;
while (*str)
result = (result << 2) ^ *str++;
return(result & MHASHAND);
}
pushinclude(str)
char *str;
{
register INCFILE *inf;
register FILE *fi;
if (fi = fopen(str, "r")) {
if (F_verbose > 1) {
#ifdef IBM
printf(" Include: %s\n", str);
#else
printf("%.*sInclude: %s\n", Inclevel*4, "", str);
#endif
}
++Inclevel;
if (F_listfile)
fprintf(FI_listfile, "------- FILE %s\n", str);
inf = (INCFILE *)zmalloc(sizeof(INCFILE));
inf->next = Incfile;
inf->name = strcpy(malloc(strlen(str)+1), str);
inf->fi = fi;
inf->lineno = 0;
Incfile = inf;
return(1);
}
printf("unable to open %s\n", str);
}
char Stopend[] = {
1,1,1,1,1,1,1,1,1,1,0,1,1,0,1,1,1,0,0,1,1
};
char *Errors[] = {
"Syntax Error",
"Expression table overflow",
"Unbalanced Braces []",
"Division by zero",
"Unknown Mnemonic",
"Illegal Addressing mode",
"Illegal forced Addressing mode", /* nu */
"Not enough args passed to Macro",
"Premature EOF",
"Illegal character",
"Branch out of range",
"ERR pseudo-op encountered",
"Origin Reverse-indexed", /* 12 */
"EQU: Value mismatch",
"Address must be <$100", /* nu */
"Illegal bit specification",
"Not enough args", /* 16 */
"Label Mismatch", /* 17 */
"Value Undefined",
"Illegal Forced Address mode", /* 19 */
"Processor not supported", /* 20 */
NULL
};
asmerr(err, abort)
short err, abort;
{
ubyte *ptr;
ubyte *str;
INCFILE *incfile;
if (Stopend[err])
StopAtEnd = 1;
for (incfile = Incfile; incfile->flags & INF_MACRO; incfile=incfile->next);
str = (ubyte *)Errors[err];
if (F_listfile)
fprintf(FI_listfile, "*line %4ld %-10s %s\n", incfile->lineno, incfile->name, str);
printf("line %4ld %-10s %s\n", incfile->lineno, incfile->name, str);
if (abort) {
puts("Aborting assembly");
if (F_listfile)
fputs("Aborting assembly\n", FI_listfile);
exit(1);
}
}
ubyte *
zmalloc(bytes)
uword bytes;
{
ubyte *ptr = malloc(bytes);
if (ptr) {
bzero(ptr, bytes);
return(ptr);
}
panic("unable to malloc");
}
ubyte *
permalloc(bytes)
uword bytes;
{
static ubyte *buf;
static int left;
ubyte *ptr;
bytes = (bytes + 1) & ~1;
if (bytes > left) {
if ((buf = malloc(ALLOCSIZE)) == NULL)
panic("unable to malloc");
bzero(buf, ALLOCSIZE);
left = ALLOCSIZE;
if (bytes > left)
panic("software error");
}
ptr = buf;
buf += bytes;
left -= bytes;
return(ptr);
}
#ifdef UNIX
xbset(s,n,c)
register ubyte *s;
register ulong n;
register ubyte c;
{
while (n--)
*s++ = c;
}
#endif
#ifdef IBM
bcmp(s,d,n)
ubyte *s, *d;
uword n;
{
uword i;
for (i = 0; i < n; ++i) {
if (s[i] != d[i])
return(0);
}
return(1);
}
#endif
\Rogue\Monster\
else
echo "will not over write src/main.c"
fi
if [ `wc -c src/main.c | awk '{printf $1}'` -ne 19306 ]
then
echo `wc -c src/main.c | awk '{print "Got " $1 ", Expected " 19306}'`
fi
echo "Finished archive 2 of 3"
# if you want to concatenate archives, remove anything after this line
exit
--
Bob Page, U of Lowell CS Dept. page@swan.ulowell.edu ulowell!page
Have five nice days.